﻿/*
 *  date: 2018-07-20
 *  author: John-chen
 *  cn: 消息控制器
 *  en: todo:
 */

using System.Collections.Generic;

namespace JyFramework
{
    /// <summary>
    /// 消息控制器
    /// </summary>
    internal class MessageCtrl : Singleton<MessageCtrl>, IEventFunction
    {
        public MessageCtrl() : base()
        {

        }

        /// <summary>
        /// 移除Manager
        /// </summary>
        public override void Remove()
        {
            RemoveAllCtrl();
        }

        /// <summary>
        /// 添加事件控制器
        /// </summary>
        /// <param name="eventCtrl"></param>
        public void AddEventCtrl(EventController eventCtrl)
        {
            if (eventCtrl == null || _eventCtrls.Contains(eventCtrl)) return;
            _eventCtrls.Add(eventCtrl);
            eventCtrl.OnInit();

            eventCtrl.OnRegistMsgEvent = RegistEvent;
            eventCtrl.OnRemoveMsgEvent = RemoveEvent;
            eventCtrl.OnNotifyEvent = NotifyEvent;
        }

        /// <summary>
        /// 移除控制器
        /// </summary>
        /// <param name="eventCtrl"></param>
        public void RemoveCtrl(EventController eventCtrl)
        {
            if (eventCtrl == null || !_eventCtrls.Contains(eventCtrl)) return;

            _eventCtrls.Remove(eventCtrl);
            eventCtrl.OnRemove();

            eventCtrl.OnRegistMsgEvent = null;
            eventCtrl.OnRemoveMsgEvent = null;
        }

        /// <summary>
        /// 移除所有的控制器
        /// </summary>
        public void RemoveAllCtrl()
        {
            if (_eventCtrls == null || _eventCtrls.Count <= 0) return;
            foreach (var ec in _eventCtrls)
            {
                ec.OnRemove();
            }
            _eventCtrls.Clear();
        }

        /// <summary>
        /// 注册事件
        /// </summary>
        /// <param name="name"></param>
        /// <param name="msg"></param>
        public void RegistEvent(string name, MessageHandler msg)
        {
            if (msg == null || _allEvents == null) return;

            List<MessageHandler> events = null;
            if (_allEvents.TryGetValue(name, out events))
            {
                events.Add(msg);
            }
            else
            {
                events = new List<MessageHandler>();
                events.Add(msg);
                _allEvents.Add(name, events);
            }
        }

        /// <summary>
        /// 通知事件
        /// </summary>
        /// <param name="name"></param>
        /// <param name="args"></param>
        public void NotifyEvent(string name, params object[] args)
        {
            if (_allEvents == null) return;
            List<MessageHandler> events = null;
            if (_allEvents.TryGetValue(name, out events))
            {
                foreach (var e in events)
                {
                    e(args);
                }
            }
            else
            {
                // log: the event is null on the notify
            }
        }

        /// <summary>
        /// 移除事件
        /// </summary>
        /// <param name="name"></param>
        /// <param name="msg"></param>
        public void RemoveEvent(string name, MessageHandler msg)
        {
            if (msg == null || _allEvents == null || !_allEvents.ContainsKey(name)) return;

            List<MessageHandler> events = null;
            if (_allEvents.TryGetValue(name, out events))
            {
                events.Remove(msg);
                if (events.Count <= 0)
                {
                    _allEvents[name].Clear();
                    _allEvents.Remove(name);
                }
            }
        }

        /// <summary>
        /// 获取EventController
        /// </summary>
        /// <returns></returns>
        public EventController GetEventController(string name = "TempEventController")
        {
            if (_eventCtrls.Count > 0) { return _eventCtrls[0]; }
            if (name == "TempEventController") { name += _eventCtrls.Count; }

            EventController ec = new EventController(name);
            AddEventCtrl(ec);

            return ec;
        }

        protected override void Init()
        {
            _eventCtrls = new List<EventController>();
            _allEvents = new Dictionary<string, List<MessageHandler>>();
        }

        protected List<EventController> _eventCtrls;
        protected Dictionary<string, List<MessageHandler>> _allEvents;
    }
}
